#include "Common.h"
#include "String.h"
#include "SharedPtr.h"
#include "ResourceManager.h"
#include "Database/DatabaseEnv.h"
#include "StringConverter.h"
#include "NGLog.h"
#include "MersenneTwister.h"
#include "ScriptMgr.h"
#include "Threading/Mutex.h"
#include "Towns.h"
#include "Game.h"
#include "Util.h"
#include "Character.h"
#include "CharManager.h"
#include "Spawns.h"
#include "PGHallManager.h"
#include "PGManualThreadsManager.h"
#include "PGWorldAIInterface.h"
#include "PGWorldAIInterface.h"
#include "PGPubStruct.h"
#include "ComputeRunTime.h"
#include "VipCardManager.h"
#include "GameDefine.h"
#include ENUM_PATH
#include LOGIC_MGR_PATH
#include XMLDATA_MGR_PATH


	
using namespace AIScript;	
PGSpawnThread::PGSpawnThread(const uint32 & nTownID, const uint32 & nNum) : ThreadBase("PGSpawnThread")
{
	mNum = nNum;
	mTownID = nTownID;	
}
//-----------------------------------------------------------------------
bool 	PGSpawnThread::run(void)
{
	uint32 nSpawnCount = 0;
	while(nSpawnCount < mNum)
	{
		Sleep(5);
		if(nSpawnCount == 0)
		{
			Log.Debug("PGSpawnThread Test","/////////Begin Spawn m_Unit[%u] SCount[%u] MaxCount[%u] p_time[%u]", 
				mTownID, nSpawnCount, mNum, now());
		}
	
		Spawn(nSpawnCount);
		nSpawnCount ++;
		
		if(nSpawnCount >= mNum)
		{
			Log.Debug("PGSpawnThread Test","/////////End Spawn m_Unit[%u] SCount[%u] MaxCount[%u] p_time[%u]", 
				mTownID, nSpawnCount, mNum, now());
		}
	}
	
	return true;
}

// //-----------------------------------------------------------------------
// void 	PGSpawnThread::Spawn(const uint32 & num)
// {
// 	CharPtr chr;
// 	Resource * pChar = sCharMgr.newDumyChar();
// 	if(!pChar)
// 		return ;
// 	Vector3 pos = sRegionMgr.getWorldRondomPosition();
// 	pChar->setFloatField("x", pos.x);
// 	pChar->setFloatField("y", pos.y);
// 	// pChar->setUInt32Field("id", RandomUInt(0,1) ? RandomUInt(401, 403) : RandomUInt(501, 503));
// 	String name = "贵宾" + StringConverter::toString(RandomUInt(1000,9999));
// 	if (!StringUtil::checkStringUTF8(name))
// 		name = StringUtil::StringToUTF8(name);
// 	pChar->setStringField("name", name);
// 	pChar->setUInt32Field("lv", 1);
// 	pChar->setUInt32Field("exps", 0);
// 	pChar->setUInt32Field("status", CharacterStatusFree);
// 	pChar->setUInt32Field("create_time", time(0));
// 	pChar->setStringField("desc", "http://192.168.0.165/gwmember/kefu/images/game_kxddz.png");
// 	pChar->setUInt32Field("isnpc", 2);
// 	chr = sCharMgr.loadCharDatabase(pChar);
// 	sCharMgr.freeDumyChar(pChar);
// 	sPubLogic.CreateItem(chr, ItemModel_Coins, sXmlDataMgr.GetConfXMLValue("ROBOT_COINS"));
// 	// sPubLogic.CreateItem(chr, en_ItemModel_RRQ, RandomUInt(700000, 1000000));

// 	TownPtr town = sTownMgr.getByHandle(!mTownID ? RandomUInt(1,3) : mTownID);
// 	if(!town.isNull())
// 	{
// 		WAITownInterface * pAITownInfe = TO_TOWN_INTERFACE(town->getAIInterface());
// 		if (NULL == pAITownInfe)
// 		{
// 			Log.Error("PGSpawnThread::Spawn", "Spawn town[%u] interface is Null", town->getHandle());
// 			return;
// 		}
// 		pAITownInfe->JoinOneChannel(chr);
// 	}
	
// 	Log.Success("PGSpawnThread Test","Spawn Chr[%u] CurrCount[%u] mTownID[%u]", chr->getHandle(), num, mTownID);
// }


LockedQueue<PGUserAuthenticInfo> PGAuthenticationQueueThread::m_authenQueue;
Threading::AtomicCounter PGAuthenticationQueueThread::m_queueCount;
//-----------------------------------------------------------------------
PGAuthenticationQueueThread::PGAuthenticationQueueThread(void)
{
	uint32 threadnum = sXmlDataMgr.GetConfXMLValue("SYN_DISPOSE_THREAD");
	m_QueueCreatePool.Startup(new PGAuthenQueueThreadRunable(), threadnum, threadnum, 0, "authenticationCreateThread"); 
}
//-----------------------------------------------------------------------
bool PGAuthenticationQueueThread::run(void)
{
	PGUserAuthenticInfo * pInfo = NULL;	
	while(true)
	{
		if(m_authenQueue.size() && m_queueCount.GetVal() <= sXmlDataMgr.GetConfXMLValue("SYN_DISPOSE_NUM"))
		{
			pInfo = new PGUserAuthenticInfo();		
			if(m_authenQueue.next_fetch(pInfo))
			{
				m_QueueCreatePool.addQueue(pInfo);
			}
			else
			{
				delete pInfo;
			}
			pInfo = NULL;
		}
		Sleep(2);
	}
	
	return true;
}

//-----------------------------------------------------------------------
bool PGAuthenQueueThreadRunable::run(void *p)
{
	++PGAuthenticationQueueThread::m_queueCount;
	PGUserAuthenticInfo* info = (PGUserAuthenticInfo*)p;
	if(NULL != info && !info->pSocket.isNull())
	{
		ComputeRunTime crt("LoginServerThread");
		crt.Start();
		sHallMgr.LoginServer(info->pSocket, info->session, info->isCenter);
		crt.End();
	}
	--PGAuthenticationQueueThread::m_queueCount;
	return true;
}

//------------------------------------------
LoadPlayerTop::LoadPlayerTop(const uint32 topType, const uint32 gzId):m_topType(topType), m_gzId(gzId)
{
	m_lstQT.clear();
}
//------------------------------------------
bool LoadPlayerTop::run()
{
	uint32 topNum = sXmlDataMgr.GetConfXMLValue("PLAYER_TOP");
	String fieldName;
	switch (m_topType)
	{
		case en_TopQueque_Coin:		// 铜钱
			fieldName = "coins";
			break;
		case en_TopQueque_Level:	// 等级
			fieldName = "lv";
			break;
		case en_TopQueque_FullWin:	// 通吃
			fieldName = "speed";
			break;
		case en_TopQueque_Flower:	// 花王
			fieldName = "defence_ext";
			break;
		case en_TopQueque_Egg:	// 蛋皇
			fieldName = "max_hp";
			break;
		case en_TopQueque_Aubergine:	// 茄圣
			fieldName = "hp";
			break;
		case en_TopQueque_BestScore:	// 单局最高
			fieldName = "speed_org";
			break;
		default:
			return true;
	}
	list<ResourcePtr> lstChars;
	if (m_gzId == 0)
	{
		if (m_topType == en_TopQueque_Level)
		{
			sCharMgr.getDBObjects(&lstChars, 0, topNum, "`isnpc` = 0 order by `lv` desc, `exps` desc");
		}
		else
		{
			sCharMgr.getDBObjects(&lstChars, 0, topNum, "`isnpc` = 0 and `%s` > 0 order by `%s` desc", fieldName.c_str(), fieldName.c_str());
		}
	}
	else
	{
		if (m_topType == en_TopQueque_Level)
		{
			sCharMgr.getDBObjects(&lstChars, 0, topNum, "`gz_id` = %u and `isnpc` = 0 order by `lv` desc, `exps` desc", m_gzId);
		}
		else
		{
			sCharMgr.getDBObjects(&lstChars, 0, topNum, "`gz_id` = %u and `isnpc` = 0 and `%s` > 0 order by `%s` desc", m_gzId, fieldName.c_str(), fieldName.c_str());
		}
	}
	list<ResourcePtr>::iterator iter = lstChars.begin();
	QueueTop qt;
	for (; iter != lstChars.end(); ++iter)
	{
		qt.id = (*iter)->getUInt32Field("serial");
		sPubLogic.FilterChars((*iter)->getStringField("name"), qt.name);
		qt.data = (*iter)->getUInt32Field(fieldName.c_str());
		XMLDataSet user_data;
		user_data.Load((*iter)->getStringField("user_data").c_str());
		qt.vipId = sVipCardMgr.GetUsedVipId(user_data);
		qt.desc = (*iter)->getStringField("desc");
		m_lstQT.push_back(qt);
	}
	sHallMgr.UpdatePlayerTop(m_gzId, m_topType, m_lstQT);
	return true;
}
